﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Graphics;

namespace DarwinIsDead.Weapons {
    class Gatling : Weapon {
        private const int NUM_BULLETS = 15;
        private const int BULLET_DAMAGE = 4;

        private const float OVERHEAT_SCALE = 0.25f;
        private const float COOLDOWN_SCALE = 0.125f;
        private const float SPREAD = (float)(Math.PI / 4.0);
        private const float DELAY = 0.05f;

        private Vector2 RELOAD_POSITION = new Vector2(0f, 40f);
        private const int RELOAD_WIDTH = 200;
        private const int RELOAD_HEIGHT = 24;
        // Reload bar
        private Texture2D reloadBar;
        private Rectangle reloadSubrect;
        private Color reloadColor;


        private Random rng;
        private int currentBullet;
        private float delayCount;
        private float overheat;

        public Gatling(World world, bool friendly) :
            base(world,
                 world.Game.Content.Load<Texture2D>("Sprites\\Weapons\\sprGatling"),
                 new Vector2(4f, 20f),
                 48f,
                 friendly) {
            for (int i = 0; i < NUM_BULLETS; i++) {
                Bullet bullet = new Bullets.Linear(World, BULLET_DAMAGE, 800f, 600f, friendly);
                Bullets.Add(bullet);
                World.AddEntity(bullet);
            }

            rng = new Random();

            currentBullet = 0;
            delayCount = 0f;
            overheat = 0f;

            reloadBar = new Texture2D(world.Game.GraphicsDevice, RELOAD_WIDTH, RELOAD_HEIGHT);
            Color[] data = new Color[RELOAD_WIDTH * RELOAD_HEIGHT];
            for (int i = 0; i < data.Length; i++) {
                data[i] = Color.White;
            }

            reloadBar.SetData(data);
            reloadSubrect = new Rectangle(0, 0, 0, RELOAD_HEIGHT);
            reloadColor = new Color(0, 0, 0);
        }

        private void Fire() {
            currentBullet = (currentBullet + 1) % Bullets.Count;

            // Fire the bullet
            Bullet bullet = Bullets[currentBullet];
            if (!bullet.Active) {
                float spread = (float)(rng.NextDouble() - 0.5 * SPREAD);
                bullet.Position = new Vector2(
                    Position.X + SpriteAxis.X + BarrelLength * (float)Math.Cos(Direction),
                    Position.Y + SpriteAxis.Y + BarrelLength * (float)Math.Sin(Direction));

                bullet.FireAngle = Direction + spread;
                bullet.Active = true;
                bullet.Solid = true;
            }
        }

        public override void InternalUpdate(GameTime gameTime) {
            MouseState mouseState = Mouse.GetState();
            float dt = (float)(gameTime.ElapsedGameTime.Milliseconds / 1000.0);

            if (mouseState.LeftButton == ButtonState.Pressed) {
                // Overheat
                if (overheat < 1f) {
                    overheat += dt * OVERHEAT_SCALE;
                    delayCount += dt;
                    if (delayCount > DELAY) {
                        Fire();
                        delayCount = 0f;
                    }
                }
            } else {
                if (overheat > 0f) {
                    overheat -= dt * COOLDOWN_SCALE;
                }
            }

            reloadSubrect.Width = (int)(overheat * RELOAD_WIDTH);
            reloadColor.R = (byte)(overheat * 255);
        }

        public override void DrawUI(SpriteBatch spriteBatch) {
            spriteBatch.Draw(reloadBar, RELOAD_POSITION, reloadSubrect, reloadColor);
        }
    }
}
